package uk.co.hs.web.security.filter;

import java.io.IOException;

import javax.servlet.FilterChain;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

import org.springframework.web.filter.GenericFilterBean;

import waffle.servlet.spi.SecurityFilterProviderCollection;
import waffle.util.AuthorizationHeader;

/**
 * WaffleNegotiateSecurityPreFilter.
 */
public class WaffleNegotiateSecurityPreFilter extends GenericFilterBean
{
  private SecurityFilterProviderCollection mProvider = null;

  /**
   * @param aProvider the provider to set
   */
  public void setProvider(SecurityFilterProviderCollection aProvider)
  {
    mProvider = aProvider;
  }

  /**
   * @see javax.servlet.Filter
   *        #doFilter(javax.servlet.ServletRequest,
   *                  javax.servlet.ServletResponse, javax.servlet.FilterChain)
   * {@inheritDoc}
   */
  public void doFilter(ServletRequest aRequest,
                       ServletResponse aResponse,
                       FilterChain aFilterChain) throws IOException, ServletException
  {
    HttpServletRequest request = (HttpServletRequest) aRequest;
    HttpServletResponse response = (HttpServletResponse) aResponse;

    HttpSession session = request.getSession(false);

    if (session != null && session.getAttribute("isAuthenticated") != null)
    {
      aFilterChain.doFilter(aRequest, aResponse);
    }
    else
    {
      AuthorizationHeader authorizationHeader = new AuthorizationHeader(request);
      if (authorizationHeader.isNull() || !mProvider.isSecurityPackageSupported(authorizationHeader.getSecurityPackage()))
      {
        try
        {
          mProvider.sendUnauthorized(response);
          response.setHeader("Connection", "keep-alive");
          response.sendError(HttpServletResponse.SC_UNAUTHORIZED);
          response.flushBuffer();
        }
        catch (Exception e)
        {
          //System.out.println("Error Sending Unauthorized response.");
        }
      }
      else
      {
        if (session != null)
        {
          session.setAttribute("isAuthenticated", Boolean.TRUE);
        }
        aFilterChain.doFilter(aRequest, aResponse);
      }
    }
  }
}
